#pragma once

#include "memory/mempool.h"

//#include "nedmalloc/nedmalloc.c"

//////////////////////////////////////////////////////////////////////////

void test_nx_alloc()
{
    nx_out(nx::ent, "check nx_alloc ->: ", nx::ent<2>);

    const int TestCont = 10000;
    const int TestLast = 1000;
    const int TestSMin = 1;
    const int TestSMax = 1024;
    const int TestDMax  = TestSMax - TestSMin + 1;

    nx::byte* test[TestLast] = {0};
    nx::size_t size[TestLast] = {0};
    clock_t t1 = 0, t2 = 0;

    /////////////////////////////////

    std::printf("TestCont: %d, TestLast: %d\nTestSize: %dByte-%.1fKB\n",
        TestCont, TestLast, TestSMin * sizeof(nx::byte), static_cast<double>(TestSMax * sizeof(nx::byte)) / 1024.0);

#if defined(NX_OS_WIN)
    system("pause");
#endif

    std::srand((unsigned)std::time(NULL));
    for(int j = 0; j < TestLast; j++)
        size[j] = (std::rand() % TestDMax) + TestSMin;

    /////////////////////////////////
    {
        std::printf("\nStart for new/delete...\t\t");
        t1 = std::clock();
        for(int i = 0; i < TestCont; i++)
        {
            for(int j = 0; j < TestLast; j++)
                test[j] = new nx::byte[size[j]];
            for(int j = 0; j < TestLast; j++)
                delete [] (test[TestLast - 1 - j]);
        }
        t2 = std::clock();
        std::printf("%lums\n", static_cast<nx::ulong>(static_cast<double>(t2 - t1) / static_cast<double>(CLOCKS_PER_SEC) * 1000.0));
    }
//    {
//        std::printf("\nStart for nedalloc...\t\t");
//        t1 = std::clock();
//        for(int i = 0; i < TestCont; i++)
//        {
//            for(int j = 0; j < TestLast; j++)
//                test[j] = (nx::byte*)nedalloc::nedmalloc(size[j]);
//            for(int j = 0; j < TestLast; j++)
//                nedalloc::nedfree(test[TestLast - 1 - j]);
//        }
//        t2 = std::clock();
//        std::printf("%lums\n", static_cast<nx::ulong>(static_cast<double>(t2 - t1) / static_cast<double>(CLOCKS_PER_SEC) * 1000.0));
//    }
    {
        nx::MemPool<> pool;
        std::printf("Start for nx::MemPool...\t");
        t1 = std::clock();
        for(int i = 0; i < TestCont; i++)
        {
            for(int j = 0; j < TestLast; j++)
                test[j] = (nx::byte*)pool.alloc(size[j]);
            for(int j = 0; j < TestLast; j++)
                pool.free(test[TestLast - 1 - j], size[TestLast - 1 - j]);
        }
        t2 = std::clock();
        std::printf("%lums\n", static_cast<nx::ulong>(static_cast<double>(t2 - t1) / static_cast<double>(CLOCKS_PER_SEC) * 1000.0));
    }
    {
        nx::FixedPool<> pool(TestSMin);
        std::printf("Start for nx::FixedPool...\t");
        t1 = std::clock();
        for(int i = 0; i < TestCont; i++)
        {
            for(int j = 0; j < TestLast; j++)
                test[j] = (nx::byte*)pool.alloc();
            for(int j = 0; j < TestLast; j++)
                pool.free(test[TestLast - 1 - j]);
        }
        t2 = std::clock();
        std::printf("%lums\n", static_cast<nx::ulong>(static_cast<double>(t2 - t1) / static_cast<double>(CLOCKS_PER_SEC) * 1000.0));
    }
    /////////////////////////////////

    nx_out(nx::ent, "check nx_alloc end", nx::ent<2>);

#if defined(NX_OS_WIN)
    system("pause");
#endif
}
